﻿using System;
using System.Collections.Generic;
using System.Reflection;
using Tinter.Common.Resources;

namespace Tinter.Common.TypeMappers
{
    /// <summary>
    /// Base class to hold type map specs for different modules.
    /// This class is intended to subclasing for each module in 
    /// solution to configure specific maps.
    /// </summary>
    public abstract class TypeMapSpecContainer
    {
        #region Properties

        private readonly Dictionary<string, ITypeMapSpec> specifications = new Dictionary<string, ITypeMapSpec>();

        /// <summary>
        /// Get the dictionary of type maps
        /// </summary>
        public Dictionary<string, ITypeMapSpec> Specifications
        {
            get
            {
                return specifications;
            }
        }

        #endregion

        #region Public Abstract Methods

        /// <summary>
        /// Register spec into this container.
        /// </summary>
        /// <typeparam name="TSource">The source type</typeparam>
        /// <typeparam name="TTarget">The target type</typeparam>
        /// <param name="spec">The spec to register</param>
        public void RegisterSpec<TSource, TTarget>(TypeMapSpecBase<TSource, TTarget> spec)
            where TSource : class
            where TTarget : class,new()
        {
            if (spec == null)
            {
                throw new ArgumentNullException(MethodBase.GetCurrentMethod().GetParameters()[0].Name);
            }

            if (string.IsNullOrEmpty(spec.Descriptor))
            {
                throw new ArgumentNullException(string.Format(
                    Messages.ExceptionCannotRegisterTypeMapperWithEmptyDescriptor,
                    spec.GetType().FullName));
            }

            specifications[spec.Descriptor] = spec;
        }

        #endregion
    }
}
